package data

import (
	"context"
	"errors"

	"medicine/internal/biz"

	"github.com/go-kratos/kratos/v2/log"
	"gorm.io/gorm"
)

// userRepo 用户数据访问实现
type userRepo struct {
	data *DataRepo
	log  *log.Helper
}

// NewUserRepo 创建用户数据访问实例
func NewUserRepo(data *DataRepo, logger log.Logger) biz.UserRepo {
	return &userRepo{
		data: data,
		log:  log.NewHelper(logger),
	}
}

// Create 创建用户
func (r *userRepo) Create(ctx context.Context, user *biz.User) error {
	result := r.data.DB.WithContext(ctx).Create(user)
	if result.Error != nil {
		r.log.Errorf("创建用户失败: %v", result.Error)
		return result.Error
	}
	return nil
}

// GetByID 根据ID获取用户
func (r *userRepo) GetByID(ctx context.Context, id int64) (*biz.User, error) {
	var user biz.User
	result := r.data.DB.WithContext(ctx).Where("id = ?", id).First(&user)
	if result.Error != nil {
		if errors.Is(result.Error, gorm.ErrRecordNotFound) {
			return nil, nil
		}
		r.log.Errorf("根据ID获取用户失败: %v", result.Error)
		return nil, result.Error
	}
	return &user, nil
}

// GetByUsername 根据用户名获取用户
func (r *userRepo) GetByUsername(ctx context.Context, username string) (*biz.User, error) {
	var user biz.User
	result := r.data.DB.WithContext(ctx).Where("username = ?", username).First(&user)
	if result.Error != nil {
		if errors.Is(result.Error, gorm.ErrRecordNotFound) {
			return nil, nil
		}
		r.log.Errorf("根据用户名获取用户失败: %v", result.Error)
		return nil, result.Error
	}
	return &user, nil
}

// Update 更新用户信息
func (r *userRepo) Update(ctx context.Context, user *biz.User) error {
	result := r.data.DB.WithContext(ctx).Save(user)
	if result.Error != nil {
		r.log.Errorf("更新用户信息失败: %v", result.Error)
		return result.Error
	}
	return nil
}

// UpdatePoints 更新用户积分
func (r *userRepo) UpdatePoints(ctx context.Context, userID int64, points int64) error {
	result := r.data.DB.WithContext(ctx).Model(&biz.User{}).
		Where("id = ?", userID).
		UpdateColumn("points", gorm.Expr("points + ?", points))
	if result.Error != nil {
		r.log.Errorf("更新用户积分失败: %v", result.Error)
		return result.Error
	}
	return nil
}

// GetByEmail 根据邮箱获取用户
func (r *userRepo) GetByEmail(ctx context.Context, email string) (*biz.User, error) {
	var user biz.User
	result := r.data.DB.WithContext(ctx).Where("email = ?", email).First(&user)
	if result.Error != nil {
		if errors.Is(result.Error, gorm.ErrRecordNotFound) {
			return nil, nil
		}
		r.log.Errorf("根据邮箱获取用户失败: %v", result.Error)
		return nil, result.Error
	}
	return &user, nil
}

// GetByPhone 根据手机号获取用户
func (r *userRepo) GetByPhone(ctx context.Context, phone string) (*biz.User, error) {
	var user biz.User
	result := r.data.DB.WithContext(ctx).Where("phone = ?", phone).First(&user)
	if result.Error != nil {
		if errors.Is(result.Error, gorm.ErrRecordNotFound) {
			return nil, nil
		}
		r.log.Errorf("根据手机号获取用户失败: %v", result.Error)
		return nil, result.Error
	}
	return &user, nil
}
